#include <iostream>
#include <signal.h>


void handlerr(int)
{
    std::cout << "接收了一次信号2" << std::endl;
    signal(2, SIG_DFL);
    std::cout << "同时恢复处理动作" << std::endl;
    std::cout << "再按忽略一次" << std::endl;
}

//signal的SIG_IHN SIG_DFL使用
void testSig01()
{
    signal(2, handlerr);
    //signal(2, SIG_IGN); //如果对signal恢复SIG_IGN动作，则该2号信号的作用会覆盖之前自定义方法的2号信号
    
    while(true)
    {
        std::cout << "等待信号ing..." << std::endl;
        sleep(1);
    }
}
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
void printPending(sigset_t& pending)
{
    printf("进程%d，pending位图：", getpid());
    for(int signo = 31; signo >= 1; signo--)
    {
        if(sigismember(&pending, signo))
            printf("1");
        else
            printf("0");
    }
    std::cout << std::endl;
}


void handler(int sig)
{
    std::cout << "——————————————————————————————————————————————————————————————————————————" << std::endl;
    std::cout << "递达" << sig << "信号!" << std::endl;
    sigset_t pending;//定义信号集
    int m = sigpending(&pending);//获取被阻塞待处理的信号集（pending信号集）
    printPending(pending);//测试信号集的更新在信号处理之后还是之前（答案是之后）
    std::cout << "——————————————————————————————————————————————————————————————————————————" << std::endl;
}


//测试信号保存相关函数，代码历程：先对二号信号进行屏蔽，10秒后解除屏蔽
void testSig02()
{
    signal(2, handler);

    //1.屏蔽2信号
    sigset_t block,oblock;
    sigemptyset(&block);
    sigemptyset(&oblock);
    //block和oblock置空

    sigaddset(&block, SIGINT);//只是将2信号加入到我们自定义的信号集中，并没有屏蔽2信号
    int n = sigprocmask(SIG_SETMASK, &block, &oblock);//这时才真正屏蔽2信号

    int cnt = 0;
    while(true)
    {
        sigset_t pending;
        int m = sigpending(&pending);

        printPending(pending);
        if(cnt == 10)
        {
            printf("解除对2信号的屏蔽\n");
            sigprocmask(SIG_SETMASK, &oblock, nullptr);
        }

        sleep(1);
        cnt++;
    }

}

int main()
{
    //testSig01();
    testSig02();
    return 0;
}